﻿using AutoMapper.Internal.Mappers;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using ThridGroup.ERP.DTO.ProductionSystem;
using Volo.Abp.Application.Dtos;
using Volo.Abp.Application.Services;
using Volo.Abp.Domain.Repositories;
using ClosedXML.Excel;
using System.IO;

namespace ThridGroup.ERP.ProductionSystem
{
    /// <summary>
    /// 工序服务实现
    /// </summary>
    public class ProcedureServices : ApplicationService, IProcedureServices
    {
        private readonly IRepository<ProcedureModel, int> _procedureRepository;

        public ProcedureServices(IRepository<ProcedureModel, int> procedureRepository)
        {
            _procedureRepository = procedureRepository;
        }

        /// <summary>
        /// 添加工序
        /// </summary>
        public async Task<int> AddProcedure(CreateProcedureDto dto)
        {
            var entity = ObjectMapper.Map<CreateProcedureDto, ProcedureModel>(dto);
            await _procedureRepository.InsertAsync(entity);
            return entity.Id;
        }

        /// <summary>
        /// 更新工序
        /// </summary>
        public async Task<int> UpdateProcedure(CreateProcedureDto dto)
        {
            if (dto.Id <= 0)
            {
                throw new ArgumentException("工序ID无效");
            }

            var entity = await _procedureRepository.FindAsync(dto.Id);
            if (entity == null)
            {
                throw new ArgumentException($"未找到ID为{dto.Id}的工序");
            }

            ObjectMapper.Map(dto, entity);
            await _procedureRepository.UpdateAsync(entity);
            return entity.Id;
        }

        /// <summary>
        /// 删除工序
        /// </summary>
        public async Task<int> DeleteProcedure(int id)
        {
            await _procedureRepository.DeleteAsync(id);
            return id;
        }

        /// <summary>
        /// 获取工序详情
        /// </summary>
        public async Task<ProcedurelistDto> GetProcedureById(int id)
        {
            var entity = await _procedureRepository.GetAsync(id);
            return ObjectMapper.Map<ProcedureModel, ProcedurelistDto>(entity);
        }

        /// <summary>
        /// 获取工序列表
        /// </summary>
        public async Task<PagedResultDto<ProcedurelistDto>> GetProcedureList(QueryProcedureDto query)
        {
            var queryable = await _procedureRepository.GetQueryableAsync();
            var result = queryable.Where(x => !x.IsDeleted);

            if (!string.IsNullOrWhiteSpace(query.ProcedureCode))
                queryable = queryable.Where(x => x.ProcedureCode.Contains(query.ProcedureCode));
            if (!string.IsNullOrWhiteSpace(query.ProcedureName))
                queryable = queryable.Where(x => x.ProcedureName.Contains(query.ProcedureName));
            if (query.IsEnable.HasValue)
                queryable = queryable.Where(x => x.IsEnable == query.IsEnable.Value);

            var totalCount = await AsyncExecuter.CountAsync(queryable);
            var items = await AsyncExecuter.ToListAsync(
                queryable.OrderByDescending(x => x.Id)
                    .Skip((query.page - 1) * query.limit)
                    .Take(query.limit)
            );

            var dtos = ObjectMapper.Map<List<ProcedureModel>, List<ProcedurelistDto>>(items);
            return new PagedResultDto<ProcedurelistDto>(totalCount, dtos);
        }

        /// <summary>
        /// 批量删除工序
        /// </summary>
        public async Task<int> BatchDeleteProcedure(List<int> ids)
        {
            if (ids == null || !ids.Any())
            {
                throw new ArgumentException("工序ID列表不能为空");
            }

            var entities = await _procedureRepository.GetListAsync(x => ids.Contains(x.Id));
            if (!entities.Any())
            {
                throw new ArgumentException("未找到要删除的工序");
            }

            await _procedureRepository.DeleteManyAsync(entities);
            return entities.Count;
        }

        /// <summary>
        /// 导出工序列表到XLSX
        /// </summary>
        public async Task<byte[]> ExportToExcel(QueryProcedureDto queryDto)
        {
            var queryable = await _procedureRepository.GetQueryableAsync();
            var result = queryable.Where(x => !x.IsDeleted);

            if (!string.IsNullOrWhiteSpace(queryDto.ProcedureCode))
                queryable = queryable.Where(x => x.ProcedureCode.Contains(queryDto.ProcedureCode));
            if (!string.IsNullOrWhiteSpace(queryDto.ProcedureName))
                queryable = queryable.Where(x => x.ProcedureName.Contains(queryDto.ProcedureName));
            if (queryDto.IsEnable.HasValue)
                queryable = queryable.Where(x => x.IsEnable == queryDto.IsEnable.Value);

            var items = await AsyncExecuter.ToListAsync(queryable.OrderByDescending(x => x.Id));
            
            using (var workbook = new XLWorkbook())
            {
                var worksheet = workbook.Worksheets.Add("工序列表");

                // 添加表头
                worksheet.Cell(1, 1).Value = "工序编码";
                worksheet.Cell(1, 2).Value = "工序名称";
                worksheet.Cell(1, 3).Value = "是否启用";
                worksheet.Cell(1, 4).Value = "备注";

                // 添加数据
                for (int i = 0; i < items.Count; i++)
                {
                    var item = items[i];
                    worksheet.Cell(i + 2, 1).Value = item.ProcedureCode;
                    worksheet.Cell(i + 2, 2).Value = item.ProcedureName;
                    worksheet.Cell(i + 2, 3).Value = item.IsEnable ? "是" : "否";
                    worksheet.Cell(i + 2, 4).Value = item.Context;
                }

                // 设置列宽
                worksheet.Columns().AdjustToContents();

                using (var stream = new MemoryStream())
                {
                    workbook.SaveAs(stream);
                    return stream.ToArray();
                }
            }
        }
    }
}
